﻿$.fn.serializeObject = function () {
    var o = {};
    var a = this.serializeArray();
    $.each(a, function () {
        if (o[this.name] !== undefined) {
            if (!o[this.name].push) {
                o[this.name] = [o[this.name]];
            }
            o[this.name].push(this.value || '');
        } else {
            o[this.name] = this.value || '';
        }
    });

    return o;
};

$.fn.putCursorAtEnd = function () {
    return this.each(function () {
        $(this).focus();

        // If this function exists...
        if (this.setSelectionRange) {
            // ... then use it (Doesn't work in IE)
            // Double the length because Opera is inconsistent about whether a carriage return is one character or two. Sigh.
            var len = $(this).val().length * 2;
            this.setSelectionRange(len, len);
        } else {
            // ... otherwise replace the contents with itself
            // (Doesn't work in Google Chrome)
            $(this).val($(this).val());
        }

        // Scroll to the bottom, in case we're in a tall textarea
        // (Necessary for Firefox and Google Chrome)
        this.scrollTop = 999999;
    });
};

var ManufacturerViewLogosViewModel = function (selfUrl, paginationUrl) {
    var self = this;

    self.prevPage = null;
    self.nextPage = null;
    self.autoLoadLimit = 5;

    var autoLoaded = 0;

    var $filterForm = null;
    var $pagesContainer = null;

    var $prevContainer = null;
    var $prevLoading = null;
    var $prevPageLoad = null;

    var $nextContainer = null;
    var $nextLoading = null;
    var $nextPageLoad = null;
    var $nextNomore = null;

    var prevXhr;
    var nextXhr;
    var filter = null;

    var loadPrevElements = function () {
        if (self.prevPage != null) {

            if (prevXhr != null) {
                prevXhr.abort();
                prevXhr = null;
            }

            $prevPageLoad.hide();
            $prevLoading.show();

            var data = $.extend({}, filter);
            data.page = self.prevPage;

            prevXhr = $.ajax({
                type: 'GET',
                cache: false,
                dataType: 'json',
                url: paginationUrl,
                data: data,
                contentType: false,
                traditional: true,
                success: function (json) {
                    if (json.IsValid) {
                        //autoLoaded++;
                        $pagesContainer.prepend(json.Data.Content);
                        $('[data-toggle="popover"]').popover();

                        if (json.Data.HasPreviousPage) {
                            self.prevPage = json.Data.Page - 1;
                            $prevPageLoad.show();
                            //setTimeout(function() {
                            //    $.force_appear();
                            //}, 1);
                        } else {
                            self.prevPage = null;
                        }
                    }
                },
                complete: function () {
                    $prevLoading.hide();
                }
            });
        }
    };

    var loadNextElements = function () {
        if (self.nextPage != null) {

            if (nextXhr != null) {
                nextXhr.abort();
                nextXhr = null;
            }

            $nextPageLoad.hide();
            $nextNomore.hide();
            $nextLoading.show();


            var data = $.extend({}, filter);
            data.page = self.nextPage;

            nextXhr = $.ajax({
                type: 'GET',
                cache: false,
                dataType: 'json',
                url: paginationUrl,
                data: data,
                contentType: false,
                traditional: true,
                success: function (json) {
                    if (json.IsValid) {
                        autoLoaded++;
                        $pagesContainer.append(json.Data.Content);
                        $('[data-toggle="popover"]').popover();

                        if (json.Data.HasNextPage) {
                            self.nextPage = json.Data.Page + 1;
                            $nextPageLoad.show();
                            setTimeout(function () {
                                $.force_appear();
                            }, 1);
                        } else {
                            self.nextPage = null;

                            if (json.Data.Page > 1) {
                                $nextNomore.fadeIn(500, function () {

                                    $nextNomore.appear();
                                    $nextNomore.one('appear', function () {
                                        delay(function () {
                                            $nextNomore.fadeOut(500);
                                        }, 1000);
                                    });
                                    $.force_appear();

                                });
                            }
                        }
                    }
                },
                complete: function () {
                    $nextLoading.hide();
                }
            });
        }
    };

    var refresh = function () {
        var newFilter = $filterForm.serializeObject();

        if (serializeObjectToUrlParameters(newFilter) === serializeObjectToUrlParameters(filter)) {
            return;
        }

        $pagesContainer.html('');

        filter = newFilter;

        //history
        var urlParams = serializeObjectToUrlParameters(filter);
        if (typeof History != 'undefined' && History.enabled) {
            //html5 compatible browsers, using history api
            History.replaceState(null, document.title, urlParams !== '' ? ('?' + urlParams) : selfUrl);
        } else {
            //in case of old browsers, reloading the page
            window.location = selfUrl + (urlParams !== '' ? ('?' + urlParams) : '');
            return;
        }

        if (!$nextContainer.is(':visible')) {
            $nextContainer.show();
        }

        autoLoaded = 0;
        self.nextPage = 1;
        loadNextElements();
    };

    var filterChanged = function (forceLoad) {

        var ms = forceLoad ? 100 : 500;

        if (forceLoad) {
            filter = null;
        }

        delay(refresh, ms);
    };

    self.init = function() {

        $filterForm = $('form[name="filter"]');
        $pagesContainer = $('#pages');

        $prevContainer = $('#prev-container');
        $prevLoading = $('.loading', $prevContainer).first();
        $prevPageLoad = $('.loadnext', $prevContainer).first();

        $nextContainer = $('#next-container');
        $nextLoading = $('.loading', $nextContainer).first();
        $nextPageLoad = $('.loadnext', $nextContainer).first();
        $nextNomore = $('.nomore', $nextContainer).first();
        filter = $filterForm.serializeObject();

        $filterForm.submit(function () {
            return false;
        });

        $(':submit', $filterForm).on('click', function () {
            filterChanged(true);
            return false;
        });

        $(':input', $filterForm).on('keypress', function (e) {
            if (e.keyCode === 13) {
                e.preventDefault();
            }
        });

        $(':input', $filterForm).on('keyup change', function (e) {
            if (e.type === 'keyup' && e.keyCode === 13) {
                filterChanged(true);
            } else {
                filterChanged(false);
            }
        });

        // There are 2 events fired on input element when clicking on the clear button:
        // mousedown and mouseup.
        $(':input', $filterForm).on('mouseup', function () {
            var $input = $(this);
            var oldValue = $input.val();

            if (oldValue === '') return;

            // When this event is fired after clicking on the clear button
            // the value is not cleared yet. We have to wait for it.
            setTimeout(function () {
                var newValue = $input.val();
                if (newValue === '') {
                    // Gotcha
                    $input.trigger("change");
                }
            }, 1);
        });

        $('a', $prevPageLoad).click(function () {
            loadPrevElements();
            return false;
        });

        $('a', $nextPageLoad).click(function () {
            loadNextElements();
            return false;
        });

        if (self.prevPage != null) {
            $prevContainer.show();
        }

        if (self.nextPage != null) {
            $nextContainer.show();
        }

        //
        var input = $(':input[name="search"]', $filterForm);
        input.putCursorAtEnd();

        $nextPageLoad.appear();
        $nextPageLoad.on('appear', function () {
            if (autoLoaded < self.autoLoadLimit) {
                $('a', $nextPageLoad).trigger('click');
            }
        });
        $.force_appear();

    };

};